查看原文
其他

一文看懂逻辑回归【比较详细】(含源码)

ShuYini AINLPer 2023-07-10

引言

对于刚刚接触深度学习的小伙伴,应该印象最深的就是线性回归和 逻辑回归了,因为一开始接触可能有很多不了解的地方,记得当时自己也是迷迷糊糊,看了CSDN的博客、吴恩达视频、李宏毅视频,最终才慢慢理解。最近突然有留言问相关内容,所以整理一下与大家分享。

关于逻辑回归的脑图如下,另外关于线性回归,大家可以看一下我之前的一篇文章:一文看懂线性回归【比较详细】(内含源码)

了解逻辑回归算法

逻辑回归也称作logistic回归分析,是一种广义的线性回归分析模型,属于机器学习中的监督学习。其推导过程与计算方式类似于回归的过程,但实际上主要是用来解决二分类问题(也可以解决多分类问题)。通过给定的n组数据(训练集)来训练模型,并在训练结束后对给定的一组或多组数据(测试集)进行分类。例如,给出一个人的身高、体重这两个指标,然后判断这个人是属于”胖“还是”瘦“;给出一个人两门课程的考试成绩,来判断这个人能不能被某某大学录取;给出神奇宝贝的两个属性值(防御值、进攻值)预测神奇宝贝属于哪一类;根据芯片检测数据来判断该芯片能否被接受等等。

逻辑回归分类

逻辑回归分类根据输入数据不同,可以分为「线性可分」分类和「非线性可分」分类。

线性可分

与线性回归法不同,逻辑回归不会尝试在给定一组输入的情况下预测数值变量的值。相反,输出是给定输入点属于某个类的概率。为简单起见,假设我们只有两个类(对于多类问题,对应的是多项Logistic回归,后面会介绍到),我们希望输出概率P大于某个值时,则判别为类别A,输出概率P小于某个值的时候判为类别B。因此,Logistic回归的输出总是在[0,1]中。

其实你也可以这么理解,线性可分就是寻找一个线性边界进行分类。对于两个维度,它是一条直线(没有弯曲),对于三维,它是一个平面,对于更高维也是一样的道理。。如下图已知蓝色和红色的数据点,根据一条直线或者平面就可以区分这些点的类别,完成分类。「其实逻辑回归线性可分和线性回归里面的单/多变量线性回归类似,只不过在原有的基础上增加了sigmod函数」

线性不可分

在实际数据中,你会发现有的数据并不能通过直线/平面等方式进行直接区分。如下图所示:为了更好的拟合数据,这个时候就需要考虑利用现有的数据点创建更多的特征数据。在这个高维特征数据上训练的逻辑回归分类器将具有更复杂的决策边界,并且在我们的二维图中绘制时将呈现非线性,这就是逻辑回归中的线性不可分。「这里和我们之前的线性回归中的多项式回归算法类似,只不过在原有的基础上增加了sigmod函数」。但是这里需要注意:虽然特征映射允许我们构建一个更具表现力的分类器,但它也更容易受到过度拟合的影响。这个时候就要用到正则化的方法了。

逻辑回归算法原理

逻辑回归既然是做分类的,那么逻辑回归怎么实现分类的呢?首先针对二分类的问题,我们希望输出输出概率P大于某个值时,则判别为类别A,输出概率P小于某个值的时候判为类别B。为此说到这里就不得不提「sigmod函数」。它的神奇之处主要是:对于任意实数,那么对应的y的取值范围为:,即将输入的任意实数映射到之间,「实现了数值到概率的转换」。具体函数为:

如上图所示,可以看出当x<0的时候,0<y<0.5,当x>0的时候,0.5<y<1。

逻辑回归的预测函数:

其中:,对于二分类来说:

将上面两个式子整合可以得到:

这样当y=1的时候则取,当y=0的时候则取。逻辑回归参数求解:上面得到了预测函数,那么我们如何求解参数呢?这里采用了最大似然估计。其中极大似然估计是数理统计中参数估计的一种重要方法。其思想就是一个事件发生了,那么发生这个事件的概率就是最大的。这里我们可以这么理解:我们有一批数据,并且他们对应的分类A,B用0,1来表示,即对应的,我们希望寻找一组参数使得每组数据发生得概率最大(最好每个数据x都和其分类一一对应)。即:
两边同取对数,因为是求式子的最大值,可以转换成式子乘以负1,之后求最小值。同时对于n个数据,累加后值会很大,之后如果用梯度下降容易导致梯度爆炸。所以可以除以样本总数n。:
其中类似于两个贝努力分布得交叉熵(用来评估两个分布的接近程度)。对求偏导得到梯度,公式如下:

正则化(增加惩罚项)

正则化项主要是对各个参数的权重做控制的函数,也叫惩罚项,它可以让整个曲线更平滑,可以有效的抑制过拟合。学习过程中,我们碰到的就是「L1正则化项、L2正则化项」,它们分别又被称为:「lasso回归项、岭回归项」

L1正则化

正则项为,限制条件为:。此时L1正则化逻辑回归的目标函数:

L1正则化梯度函数为(绝对值求导分类两种情况):

「L1有一个特殊的功能:它可以稀疏化的取值,即会让某些值为0」。原因解释:如下图2所示,当有两个变量(对应图中的w1,w2)的时候,圆环和正方形的交点是最合适的点是正方形的角点,当取到角点的时候此时的为0,扩展到有三个参数的时候,最合适的点也最有可能在角点上,此时另外两个变量为0,同样扩展到多维如图3所示也是一个到道理)。

L2正则

其正则化项为:,限制条件为:。此时L2正则化逻辑回归的目标函数:

L2正则化逻辑回归的梯度函数如下:

L1和L2使用说明

  • L1正则化可以产生稀疏权值矩阵,即产生一个稀疏模型,可以用于特征选择;

  • L2正则化可以防止模型过拟合,在一定程度上,L1也可以防止过拟合,提升模型的泛化能力;

  • L1(lasso)正则假设参数的先验分布是Laplace分布,可以保证模型的稀疏性,也就是某些参数等于0;

  • L2(岭回归)正则假设参数的先验分布是Gaussian分布,可以保证模型的稳定性,也就是参数的值不会太大或太小。

    在实际使用中,如果特征是高维稀疏的,则使用L1正则;如果特征是低维稠密的,则使用L2正则

代码实现

代码实现主要包含两个部分,一个是线性可分的情况,另外一个线性不可分情况。其中线性可分是利用吴恩达的数据集(根据两门考试成绩来判断是否被录用),线性不可分的数据集(根据芯片检测的打分,来判断是否通过核检)。

线性可分

读取得到数据点,如下图所示:代码实现如下图所示:(需要完整代码可以联系作者)

epoches=200000
batch_size=100
theta=np.zeros((3,1))
alpha=0.003
costfunres=[]
theta,costfunres=gradientDescent(x,y,theta,epoches,alpha,batch_size,costfunres)
print(theta)
plt.figure(figsize=(10,5))
ax=plt.subplot(1,2,1)
ax.axis([20,110,20,110])
ax.scatter(data[data['Accepted']==0]['Exam 1'],data[data['Accepted']==0]['Exam 2'],c='black',marker='x',label='No Admitted')
ax.scatter(data[data['Accepted']==1]['Exam 1'],data[data['Accepted']==1]['Exam 2'],c='y',marker='o',label='Admitted')
ax.legend(loc=1)
ax.set(xlabel='Exam1', ylabel='Exam2')
ex1=np.linspace(20,110,100)
ex2=-(theta[0]/theta[2]+theta[1]/theta[2]*ex1)
plt.plot(ex1,ex2,'r-')
plt.show()

实验结果如下图:

线性不可分

当给的数据不能够通过线性边界(直线、平面等)进行区分的时候(入下图所示),为了更好的拟合数据,这个时候就需要考虑从每个数据点创建更多的特征。在这个高维特征向量上训练的逻辑回归分类器将具有更复杂的决策边界,并且在我们的二维图中绘制时将呈现非线性,这就是逻辑回归中的线性不可分。下面是具体的代码实现((需要完整代码可以联系作者)):

 # 模型训练及并画出结果曲线
lr=0.001
lamda=0.05 # 惩罚权重越大,容易出现欠拟合,惩罚权重越小,容易出现过拟合。
epoches=200000
batch_size=118
theta,loss_cost=no_line_train(x_f,y_f,lr,epoches,batch_size,lamda)
x=np.linspace(-1.2,1.2,200)
xx,yy=np.meshgrid(x,x)
x_plot=feature_mapping(xx.ravel(),yy.ravel(),6).values
zz=x_plot@theta
zz=zz.reshape(xx.shape)

plt.figure(figsize=(6,5))
ax=plt.subplot()
ax.scatter(data[data['accepted']==1]['data1'],data[data['accepted']==1]['data2'],marker='o',c='black',label='accepted')
ax.scatter(data[data['accepted']==0]['data1'],data[data['accepted']==0]['data2'],marker='x',c='y',label='unaccepted')
ax.legend(loc=1)
ax.set(xlabel='data1',ylabel='data2')
ax.contour(xx,yy,zz,0,colors=['red'])
plt.show()

实验结果如下:

逻辑回归和线性回归的区别

这应该是初学者比较困惑的问题。逻辑回归是在线性回归的基础上加了一个 Sigmoid 函数(非线形)映射,使得逻辑回归称为了一个优秀的分类算法。本质上来说,两者都属于广义线性模型,但它们两个要解决的问题不一样,「逻辑回归解决的是分类问题,输出的是离散值,线性回归解决的是回归问题,输出的连续值」。在脑图中可以看到,逻辑回归中的线性可分、线性不可分分别对应线性回归中的单/多变量线性回归、多项式回归。

参考文献

[1] https://blog.csdn.net/weixin_60737527/article/details/124141293

[2] https://zhuanlan.zhihu.com/p/74874291

[3] https://cloud.tencent.com/developer/article/1412823

[4] https://zhuanlan.zhihu.com/p/352437358

推荐阅读

[1]必看!!【AINLPer】自然语言处理(NLP)领域知识&&资料大分享

[2]【NLP论文分享&&文本生成】基于Transformer的变分自动编码器(VAE)(清华大学含源码)

[3]【NLP论文分享&&源码】多修辞文本生成(nFLAG)

[3] 一文看懂线性回归【比较详细】(内含源码)

点击下方链接🔗关注我们

资料整理不易,帮忙点个在看




您可能也对以下帖子感兴趣

文章有问题?点此查看未经处理的缓存